<?php
namespace Service\WebSocketService\WebSocketRouter;

use Service\BaseService;
use App\Model\CommodityModel\CommodityArchives;
use Hyperf\DbConnection\Db;
use Service\Code\Normal;
use App\Model\PssModel\OrderSupplier;

/**
 * 年度销售报表
 * @author huj
 */
class YearSaleOrderSocketService extends BaseService {

    public $server;

    public $fd;

    /**
     * 年度销售报表
     * @param object $server
     * @param int $fd
     * @param array $data
     * @param array $sysInfo
     * @param array $excel_hedaer
     * @param array $excel_data
     * @return mixed|array
     */
    public function yearSaleOrderReport($server, int $fd, array $data, array $sysInfo, array $excel_hedaer, array $excel_data) {
        $this->server            = $server;
        $this->fd                = $fd;
        $year                    = self::getSearchParam($data);
        $monthList               = self::getMonthList($year);
        $importData              = [];
        $totalOrder              = 0; //总订单数（不含售后）
        $totalSupplierSettlement = 0; //总供应商结算金额
        $totalUserSettlement     = 0; //总渠道结算金额
        $totalOrderMoney         = 0; //总订单金额
        foreach ($monthList as $key => $month) {
            $userResult              = self::getUserResult($month);
            $supplierResult          = self::getSupplierResult($month);
            $importData[]            = [
                $month,
                $supplierResult ? $supplierResult['order_count'] : 0,
                $supplierResult ? number_format($supplierResult['total_settlement_money'], 2) : 0.00,
                $userResult ? number_format($userResult['total_settlement_money'], 2) : 0.00,
                $supplierResult ? number_format($supplierResult['total_money'], 2) : 0.00,
            ];
            $totalOrder              += $supplierResult ? $supplierResult['order_count'] : 0;
            $totalSupplierSettlement += $supplierResult ? $supplierResult['total_settlement_money'] : 0.00;
            $totalUserSettlement     += $userResult ? $userResult['total_settlement_money'] : 0.00;
            $totalOrderMoney         += $supplierResult ? $supplierResult['total_money'] : 0.00;
            //进度
            $send = Normal::returnWsStatus(Normal::WS_START, "进行中", [
                'percent' => 8 * ($key + 1),
            ]);
            $send = json_encode($send, JSON_UNESCAPED_UNICODE);
            $this->server->push($this->fd, $send);

        }
        $sumRow = ['合计', $totalOrder, number_format($totalSupplierSettlement, 2), number_format($totalUserSettlement, 2), number_format($totalOrderMoney, 2)];
        array_push($importData, $sumRow);
        //数据准备完成开始写入excel本地数据
        $send = Normal::returnWsStatus(Normal::WS_START, "进行中", [
            'percent' => 98.00,
        ]);
        $send = json_encode($send, JSON_UNESCAPED_UNICODE);
        $this->server->push($this->fd, $send);

        //开始导出数据
        $result_export = \exportFile(self::getColumns(), $importData, $year . "年度销售报表");
        $importData    = [];
        //导出异常
        if ($result_export['code'] != Normal::SUC) {
            return Normal::returnWsStatus(Normal::WS_ERROR, $result_export['msg']);
        }

        return Normal::returnWsStatus(Normal::WS_END, "已完成", [
            'percent'      => 100.00,
            'download_url' => $result_export['data']['url'] ?? '',
        ]);
    }

    /**
     * 获取公共查询参数
     * @param string $month
     * @return mixed
     * @author huj
     */
    public static function getQueryModel($month, $type, $order_type = 0) {
        if ($type == 1) {
            $filed = "IFNULL(sum(IF(os.order_type = 0,osm.settlement_money,os.real_total_money)), 0.00) AS total_settlement_money";
        } else {
            $filed = "IFNULL(sum(osm.settlement_money),0.00) AS total_settlement_money";
        }
        $monthTimeStamp = self::getMonthTime($month);
        $field          = [
            'COUNT(os.id) AS order_count',
            'IFNULL(SUM(os.real_total_money),0.00) AS total_money',
            "FROM_UNIXTIME(os.cd, '%Y-%m') AS m",
            $filed
        ];
        $query          = OrderSupplier::query()->from((new OrderSupplier)->getTable() . ' as os')->selectRaw(implode(',', $field))
            ->where('os.cd', '>=', $monthTimeStamp['startTime'])
            ->where('os.cd', '<=', $monthTimeStamp['endTime'])
            ->where('os.order_push_status', 1)
            ->where('os.after_sale_status', 0);
        if ($order_type == SHOP_SELF_BONDED_ORDER) {
            $query->where('os.order_type', $order_type);
        } else {
            $query->where('os.order_type', '!=', $order_type);
        }

        return $query;
    }

    /**
     * 获取渠道商的统计结果
     * @param string $month
     * @return mixed
     * @author huj
     */
    public static function getUserResult($month, $order_type = 0) {
        return self::getQueryModel($month, 1, $order_type)->leftJoin('order_settlement as osm', function ($join) {
            $join->on('os.id', '=', 'osm.order_id')->where('osm.settlement_type', 1)->where('osm.settlement_mode', 1);
        })->first();
        // ->leftJoin('order_settlement as osm', 'os.id = osm.order_id AND osm.settlement_type = 1 AND osm.settlement_mode = 1')->find();

    }

    /**
     * 获取供应商的统计结果
     * @param string $month
     * @return mixed
     * @author huj
     */
    public static function getSupplierResult($month, $order_type = 0) {
        return self::getQueryModel($month, 2, $order_type)->leftJoin('order_settlement as osm', function ($join) {
            $join->on('os.id', '=', 'osm.order_id')->where('osm.settlement_type', 2)->where('osm.settlement_mode', 1);
        })->first();
        // ->leftJoin('order_settlement osm', 'os.id = osm.order_id AND osm.settlement_type = 2 AND osm.settlement_mode = 1')->find();
    }

    /**
     * 获取搜索参数
     * @param array $params
     * @return string
     * @author huj
     */
    public static function getSearchParam($params) {
        $year = date('Y');
        if ((isset($params['year']) || !empty($params['year'])) && ctype_digit((string)$params['year'])) {
            $year = $params['year'];
        }
        if ((isset($params['create_time']) || !empty($params['create_time'])) && false !== strtotime($params['create_time'])) {
            $year = date('Y', strtotime($params['create_time']));
        }
        return $year;
    }

    /**
     * 获取excel表头字段
     * @return array
     * @author huj
     */
    public static function getColumns() {
        return [
            '所属时间',
            '订单数（不含售后）',
            '供应商结算金额',
            '渠道结算金额',
            '订单金额',
        ];
    }

    /**
     * 获取某年的所有月份
     * @param string $year
     * @return array
     * @author huj
     */
    public static function getMonthList($year) {
        if (empty($year) || !ctype_digit((string)$year)) {
            $year = date('Y');
        }
        $firstMonth = date($year . '-01');
        $lastMonth  = date($year . '-12');
        $begin      = new \DateTime($firstMonth);
        $end        = new \DateTime($lastMonth);
        $end        = $end->modify('+1 month');
        // $interval   = new DateInterval('P1M');
        $interval  = \DateInterval::createFromDateString('+1 month');
        $dateRange = new \DatePeriod($begin, $interval, $end);
        $monthList = [];
        foreach ($dateRange as $date) {
            $monthList[] = $date->format("Y-m");
        }
        return $monthList;
    }

    /**
     * 获取某个月第一天和最后一天的时间戳
     * @return array
     * @author huj
     * @DateTime 2022-02-10 10:17:40
     */
    public static function getMonthTime($month) {
        $firstDay  = date('Y-m-01 H:i:s', strtotime($month));
        $lastDay   = date('Y-m-d H:i:s', strtotime($firstDay . '+1 month'));
        $startTime = strtotime($firstDay);
        $endTime   = strtotime($lastDay) - 1;
        return [
            'startTime' => $startTime,
            'endTime'   => $endTime,
        ];
    }
}